﻿/**
 * Peter
 * Created by: Peter Development Team
 *    http://peter.codeplex.com/
 * 
 * GNU General Public License version 2 (GPLv2)
 *    http://peter.codeplex.com/license
 *
 *  This code is provided on an AS IS basis, with no WARRANTIES,
 *  CONDITIONS or GUARANTEES of any kind.
 *  
 **/

using System.Collections.Specialized;
using System.ComponentModel;
using System.Windows;
using Peter.Common;
using Peter.Common.Utilities;
using Peter.Data;
using Peter.Logic;
using Peter.Logic.Dialogs;
using Peter.Properties;
using Peter.View;
using System.IO;
using Peter.View.Dialogs;
using Xceed.Wpf.AvalonDock.Layout.Serialization;

namespace Peter
{
   /// <summary>
   /// The main window for Peter.
   /// </summary>
   public partial class MainWindow
   {
      private const string LAYOUT_FILE = "Layout.xml";

      /// <summary>
      /// Initializes a new main window.
      /// </summary>
      public MainWindow ()
      {
         InitializeComponent ();
         this.Loaded += this.MainLoaded;
         this.Closing += this.MainClosing;
      }

      /// <summary>
      /// Event occurs when the main window has been loaded.
      /// </summary>
      /// <param name="sender">The main window.</param>
      /// <param name="e">RoutedEventArgs</param>
      private void MainLoaded (object sender, RoutedEventArgs e)
      {
         InitializeSettings ();
         this.Loaded -= this.MainLoaded;
         if (this.DataContext != null)
         {
            ViewRegistry.Register (typeof (ModelAbout), typeof (ViewAbout));
            ViewRegistry.Register (typeof (OptionsEditor), typeof (ViewOptionsEditor));
            ViewRegistry.Register (typeof (OptionsGeneral), typeof (ViewOptionsGeneral));
            ViewRegistry.Register (typeof (ModelMessageDialog), typeof (ViewMessageDialog));

            var vm = (ModelPeterMain)this.DataContext;
            this.CommandBindings.AddRange (vm.CommandBindings);
            this.InputBindings.AddRange (vm.InputBindings);
            vm.Initialize ();

            MenuItems.SetRecentFileCollection ();
            LoadSettings ();
         }
      }

      /// <summary>
      /// Initializes variables in the settings object.
      /// </summary>
      private static void InitializeSettings ()
      {
         if (Settings.Default.StartupFiles == null)
            Settings.Default.StartupFiles = new StringCollection ();
         if (Settings.Default.RecentFiles == null)
            Settings.Default.RecentFiles = new StringCollection ();
      }

      /// <summary>
      /// Event occurs when the main window is closing.
      /// </summary>
      /// <param name="sender">The main window.</param>
      /// <param name="e">CancelEventArgs</param>
      private void MainClosing (object sender, CancelEventArgs e)
      {
         if (this.DataContext != null)
         {
            var vm = (ModelPeterMain)this.DataContext;
            if (vm.Close ())
            {
               this.Closing -= this.MainClosing;
               SaveSettings ();
            }
            else
            {
               e.Cancel = true;
            }
         }
      }

      /// <summary>
      /// Event occurs when some files are dropped.
      /// </summary>
      /// <param name="sender">The main window.</param>
      /// <param name="e">DragEventArgs</param>
      private void OnDropEvent (object sender, DragEventArgs e)
      {
         //check if the objects dropped could be converted in a specific format
         if (e.Data.GetDataPresent (DataFormats.FileDrop, true))
         {
            //get the paths of the files dropped after the conversion
            var droppedFilesPaths = e.Data.GetData (DataFormats.FileDrop, true) as string[];

            if (this.DataContext != null)
            {
               var vm = (ModelPeterMain)this.DataContext;
               vm.HandleDroppedFiles (droppedFilesPaths);
            }
         }
      }

      /// <summary>
      /// Saves the docking layout.
      /// </summary>
      private void SaveSettings ()
      {
         var layoutFile = Path.Combine (CommonUtilities.GetAssemblyDirectory (), LAYOUT_FILE);
         if (Settings.Default.SaveLayoutOnExit)
         {
            var serializer = new XmlLayoutSerializer (this._DockMan);
            using (var stream = new StreamWriter (layoutFile))
            {
               serializer.Serialize (stream);
            }
         }
      }

      /// <summary>
      /// Loads the last layout.
      /// </summary>
      private void LoadSettings ()
      {
         var vm = (ModelPeterMain) this.DataContext;
         if (Settings.Default.SaveLayoutOnExit)
         {
            var layoutFile = Path.Combine (CommonUtilities.GetAssemblyDirectory (), LAYOUT_FILE);
            if (File.Exists (layoutFile))
            {
               var serializer = new XmlLayoutSerializer (this._DockMan);
               using (var stream = new StreamReader (layoutFile))
               {
                  //====================================================
                  // Subscribing to the LayoutSerializationCallback is
                  // used to be able to load the AvalonDock layout.
                  // When this is not used, the layout is not loaded.
                  //====================================================
                  serializer.LayoutSerializationCallback += vm.DockDeserializationCallback;
                  serializer.Deserialize (stream);
               }
               serializer.LayoutSerializationCallback -= vm.DockDeserializationCallback;
            }
            if (vm.Documents.Count == 0)
               vm.NewFile ();
         }
         else if (Settings.Default.StartupBlankDoc)
         {
            vm.NewFile ();
         }
         else if (Settings.Default.StartupSpecificDocs)
         {
            foreach (var startupFile in Settings.Default.StartupFiles)
               vm.OpenFile (startupFile);
         }
      }
   }
}
